<?php
/**
 * Created by PhpStorm.
 * User: Inhere
 * Date: 2015/3/4
 * Time: 19:44
 * Usage : 一个数据库的信息数据，包含了对当前数据库的各种操作，数据库的表信息(AbstractTable)
 * File: AbstractDatabase.php
 */

namespace ulue\core\db\base\command;


use ulue\core\db\base\AbstractDbDriver;

abstract class AbstractDatabase extends AbstractCommand
{
    /**
     * Property name.
     * ['table name'=> AbstractTable]
     * @var  array
     */
    protected $_tbs       = [];

    /**
     * Property name.
     * current database all table names;
     * @var  array
     */
    protected $_tbNames   = [];

    /**
     * Property name.
     * current database all table status details;
     * @var  array
     */
    protected $_tbDetails = [];


    public function __construct($name='', AbstractDbDriver $db=null)
    {
        $this->name = $name;
        $this->db   = $db;
    }

    abstract public function select();

    abstract public function rename($newName, $returnNew = true);

    abstract public function setCharset($charset='utf8');

    /**
     * getTables
     * @param  boolean $refresh
     * @return array @see $_tbNames
     */
    abstract public function getTableNames($refresh=false);

    /**
     * @param string $table
     * @return AbstractTable
     */
    abstract public function getTable($table);

    /**
     * @return array[] @see $_tbDetails
     */
    abstract public function getTableDetails();

    /**
     * 表的信息 如 Engine/ Collation /Comment 等
     * @param  string $table
     * @param bool $refresh
     * @return array
     */
    abstract public function getTableDetail($table, $refresh=false);

    abstract public function tableExists($name);

    /**
     * 添加新用户
     * mysql: grant select,insert,update,delete on *.* to username@localhost identified by 'password';
     * 注：
     *      [*.*]     [数据库名.表名] > 限制只能登录某一个数据库 test.*
     *      username  是用户名
     *      localhost 是本地主机 网络可以使用 '%'代替所有主机
     *      password  是密码
     *      所有权限可以用 all代替
     * @param $user
     * @param array $param
     * @return mixed
     */
    public function addUser($user, array $param)
    {
        $pwd        = empty( $param['pwd'] ) ? '123456'     : trim($param['pwd']);
        $host       = empty( $param['host'] ) ? 'localhost' : trim($param['host']);
        $dbAndTbl   = empty( $param['db_tbl'] ) ? '*.*'     : trim($param['db_tbl']);
        $auth       = empty( $param['auth'] ) ? 'ALL'       : trim($param['auth']);

        $addUserSql = "GRANT {$auth} ON {$dbAndTbl} TO {$user}@{$host} IDENTIFIED BY '{$pwd}'";

        return $this->db->setSql($addUserSql)->execute();
    }

    /**
     * 删除用户
     * mysql: delete from mysql.user where user='wangwu' and host='localhost';
     * @param $user
     * @param string $host
     * @return mixed
     */
    public function delUser($user, $host = 'localhost')
    {
        $mysqlUser  = '`mysql`.`user`';
        $delUserSql = "DELETE FROM {$mysqlUser} WHERE `user`='{$user}' AND `host`='{$host}'";

        return $this->db->bySql($delUserSql)->execute();
    }

    /**
     * 查看用户权限
     * mysql: SHOW GRANTS FOR root@localhost;
     * @param string $user
     * @param string $host
     * @return array
     */
    public function showGrant($user = 'root', $host = 'localhost')
    {
        return $this->db->setSql("SHOW GRANTS FOR '{$user}'@'{$host}'")->queryAll();
    }

    /**
     * 移除权限
     * mysql: revoke all on *.* from root@localhost;
     * @param string $user
     * @param array $param
     * @return mixed
     */
    public function revoke($user, array $param)
    {
        $host       = empty( $param['host'] ) ? 'localhost' : trim($param['host']);
        $dbAndTbl   = empty( $param['db_tbl'] ) ? '*.*'     : trim($param['db_tbl']);
        $auth       = empty( $param['auth'] ) ? 'ALL'       : trim($param['auth']);

        return $this->db->bySql("REVOKE {$auth} ON {$dbAndTbl} FROM {$user}@{$host}")->execute();
    }

    public function addQuote($name)
    {
        return "`{$name}`";
    }


}// end class AbstractDatabase